﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web;
using System.Net;
using System.Net.Sockets;
using System.IO;
using System.Threading;

using log4net;
using log4net.Config;
using System.Reflection;

namespace AutoRule
{
    class CHttpServer
    {
        public void Run()
        {
            ILog log = log4net.LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
            HttpListener listerner = new HttpListener();
            try
            {
                string AddressIP = string.Empty;
                foreach (IPAddress _IPAddress in Dns.GetHostEntry(Dns.GetHostName()).AddressList)
                {
                    if (_IPAddress.AddressFamily.ToString() == "InterNetwork")
                    {
                        AddressIP = _IPAddress.ToString();
                    }
                }

        
                listerner.AuthenticationSchemes = AuthenticationSchemes.Anonymous;//指定身份验证 Anonymous匿名访问
                listerner.Prefixes.Add("http://" + AddressIP + ":" + CConfig.GetInstance()._localserverport + "/Data/");
                listerner.Start();
            }
            catch (Exception exception)
            {
                
                log.Error("httpserver", exception);
                Environment.Exit(0);
            }

            log.Debug("httpserver start ok");

                int maxThreadNum, portThreadNum;

                //线程池
                int minThreadNum;
                ThreadPool.GetMaxThreads(out maxThreadNum, out portThreadNum);
                ThreadPool.GetMinThreads(out minThreadNum, out portThreadNum);
                while (true)
                {
                    //等待请求连接
                    //没有请求则GetContext处于阻塞状态

                    HttpListenerContext ctx = listerner.GetContext();

                    ThreadPool.QueueUserWorkItem(new WaitCallback(TaskProc), ctx);
                }
                //Console.Clear();
                //listerner.Stop();
            
        }

        private static void TaskProc(object o)
        {
            HttpListenerContext ctx = (HttpListenerContext)o;

            ctx.Response.StatusCode = 200;//设置返回给客服端http状态代码
            ctx.Response.AddHeader("Access-Control-Allow-Origin", "*");

            string varName = System.Web.HttpUtility.UrlDecode(Request(ctx.Request), Encoding.GetEncoding("utf-8"));
            if (varName == "update")
            {
                using (StreamWriter writer = new StreamWriter(ctx.Response.OutputStream, Encoding.UTF8))
                {
                    CTimerRuleManager.GetInstance().Parse();

                    writer.Write("success");
                    writer.Close();
                    ctx.Response.Close();
                }
                ILog log = log4net.LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
                log.Debug("httpserver update ok");
            }
            else if (varName == "getinfo")
            {
                using (StreamWriter writer = new StreamWriter(ctx.Response.OutputStream, Encoding.UTF8))
                {
                    String info = CObserver.GetInstance().GetInfo();

                    writer.Write(info);
                    writer.Close();
                    ctx.Response.Close();
                }
                ILog log = log4net.LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
                log.Debug("get info ok");
            }
            //else if (varName == "exit")
            //{
            //    using (StreamWriter writer = new StreamWriter(ctx.Response.OutputStream, Encoding.UTF8))
            //    {
            //        wholeAction = "exit";
            //        writer.Write("exit");
            //        writer.Close();
            //        ctx.Response.Close();
            //    }
            //}
            else
            {
                using (StreamWriter writer = new StreamWriter(ctx.Response.OutputStream, Encoding.UTF8))
                {
                    writer.Write("false");
                    writer.Close();
                    ctx.Response.Close();
                }
                ILog log = log4net.LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
                log.Debug("http server undefine action");
            }
        }

        static string Request(HttpListenerRequest request)
        {
            string temp = "this is a test!";
            if (request.HttpMethod.ToLower().Equals("get"))
            {
                //GET请求处理
                if (!string.IsNullOrEmpty(request.QueryString["action"]))
                    temp = request.QueryString["action"];
            }
            else if (request.HttpMethod.ToLower().Equals("post"))
            {
                Stream SourceStream = request.InputStream;
                byte[] currentChunk = ReadLineAsBytes(SourceStream);
                //获取数据中有空白符需要去掉，输出的就是post请求的参数字符串 如：username=linezero
                temp = Encoding.Default.GetString(currentChunk).Replace("", "");
            }
            return temp;
        }

        static byte[] ReadLineAsBytes(Stream SourceStream)
        {
            var resultStream = new MemoryStream();
            while (true)
            {
                int data = SourceStream.ReadByte();
                resultStream.WriteByte((byte)data);
                if (data <= 10)
                    break;
            }
            resultStream.Position = 0;
            byte[] dataBytes = new byte[resultStream.Length];
            resultStream.Read(dataBytes, 0, dataBytes.Length);
            return dataBytes;
        }
    }
}
